#include <stdio.h>

#include <stdlib.h>

#include <sys/socket.h>

#include <string.h>

#include <linux/netlink.h>



#define NETLINK_TEST 22

#define MSG_LEN 100



struct msg_to_kernel

{

    struct nlmsghdr hdr;

    char data[MSG_LEN];

};

struct u_packet_info

{

    struct nlmsghdr hdr;

    char msg[MSG_LEN];

};



int main(int argc, char* argv[]) 

{

    char *data = "This message is from eric's space";

    //³õ¯

    struct sockaddr_nl local;

    struct sockaddr_nl kpeer;

    int skfd, ret, kpeerlen = sizeof(struct sockaddr_nl);

    struct nlmsghdr *message;

    struct u_packet_info info;

    char *retval;

    message = (struct nlmsghdr *)malloc(1);



    skfd = socket(PF_NETLINK, SOCK_RAW, NETLINK_TEST);

    if(skfd < 0){

        printf("can not create a netlink socket\n");

        return -1;

    }

    memset(&local, 0, sizeof(local));

    local.nl_family = AF_NETLINK;

    local.nl_pid = getpid();

    local.nl_groups = 0;

    if(bind(skfd, (struct sockaddr *)&local, sizeof(local)) != 0){

        printf("bind() error\n");

        return -1;

    }

    memset(&kpeer, 0, sizeof(kpeer));

    kpeer.nl_family = AF_NETLINK;

    kpeer.nl_pid = 0;

    kpeer.nl_groups = 0;



    memset(message, '\0', sizeof(struct nlmsghdr));

    message->nlmsg_len = NLMSG_SPACE(strlen(data));

    message->nlmsg_flags = 0;

    message->nlmsg_type = 0;

    message->nlmsg_seq = 0;

    message->nlmsg_pid = local.nl_pid;



    retval = memcpy(NLMSG_DATA(message), data, strlen(data));



    printf("message sendto kernel are:%s, len:%d\n", (char *)NLMSG_DATA(message), message->nlmsg_len);

    ret = sendto(skfd, message, message->nlmsg_len, 0,(struct sockaddr *)&kpeer, sizeof(kpeer));

    if(!ret){

        perror("send pid:");

        exit(-1);

    }



    //½ÓÜںË¬ȷÈÐϢ

    ret = recvfrom(skfd, &info, sizeof(struct u_packet_info),0, (struct sockaddr*)&kpeer, &kpeerlen);

    if(!ret){

        perror("recv form kerner:");

        exit(-1);

    }



    printf("message receive from kernel:%s\n",(char *)info.msg);

    //Äº˺Íû§½øÐ



    close(skfd);

    return 0;

}

